#pragma once

#include <stddef.h>

namespace l8
{

#if defined(ENABLE_LOGGING)
class Logger
{
public:
    // Acquires resources for logging if the right flags are set.
    static bool Setup();

    // Frees resources acquired in Setup.
    static void TearDown();

    static bool logging_enabled() {
        return m_logging_enabled;
    }

    // Write a raw string to the log to be used as a preamble.
    // No check is made that the 'preamble' is actually at the beginning
    // of the log. The preample is used to write code events saved in the
    // snapshot.
    static void Preamble(const char* content);

    // Emits an event with a string value -> (name, value).
    static void StringEvent(const char* name, const char* value);

    // Emits an event with an int value -> (name, value).
    static void IntEvent(const char* name, int value);

    // Emits memory management events for C allocated structures.
    static void NewEvent(const char* name, void* object, size_t size);
    static void DeleteEvent(const char* name, void* object);

private:
    Logger();
    Logger(const Logger&);

    static bool m_logging_enabled;
};

#define SETUP_LOG() l8::Logger::Setup()
#define TEAR_DOWN_LOG() l8::Logger::TearDown()

#define LOG(Call) \
    if (l8::Logger::logging_enabled()) \
    { \
        l8::Logger::Call; \
    }

#else // ENABLE_LOGGING not defined

#define SETUP_LOG()
#define TEAR_DOWN_LOG()

#define LOG(message)

#endif // #if ENABLE_LOGGING

} // namespace l8
